Support recent change moving virtual IOAPIC model into Xen for
authorkaf24@firebug.cl.cam.ac.uk <kaf24@firebug.cl.cam.ac.uk>
Wed, 9 Nov 2005 13:53:12 +0000 (14:53 +0100)
committerkaf24@firebug.cl.cam.ac.uk <kaf24@firebug.cl.cam.ac.uk>
Wed, 9 Nov 2005 13:53:12 +0000 (14:53 +0100)
ia64/VTI. Now ia64/vti will create links to arch/x86/dm/vmx_vioapic.c
and include/x86/vmx_vlapic.h.

Firstly, a small change to common virtual IOAPIC model to be used by
both sides. Also some compilation fix to tools is included in first
one. Secondly, there are ia64-specific changes to hook to common
IOAPIC model.

Based on this patch upon latest xen-ia64-unstable tip, we can see
multiple domains working again on XEN/IA64, including both domU and
VTI domain simultaneously in run-time.

Signed-off-by Kevin Tian <kevin.tian@intel.com>
Signed-off-by Anthony Xu <Anthony.xu@intel.com>
Signed-off-by Yunhong Jiang <yunhong.jiang@intel.com>
Signed-off-by Eddie Dong <eddie.dong@intel.com>

20 files changed:
tools/examples/xmexample.vti
tools/ioemu/ia64_intrinsic.h
tools/ioemu/target-i386-dm/Makefile
tools/ioemu/vl.c
tools/libxc/xc_ia64_stubs.c
tools/libxc/xc_linux_build.c
xen/arch/ia64/Makefile
xen/arch/ia64/Rules.mk
xen/arch/ia64/vmx/mmio.c
xen/arch/ia64/vmx/vlsapic.c
xen/arch/ia64/vmx/vmx_init.c
xen/arch/ia64/vmx/vmx_support.c
xen/arch/ia64/xen/domain.c
xen/arch/x86/dm/vmx_vioapic.c
xen/include/asm-ia64/vmx.h
xen/include/asm-ia64/vmx_platform.h
xen/include/asm-ia64/vmx_vcpu.h
xen/include/asm-ia64/vmx_vpd.h
xen/include/asm-x86/vmx_vioapic.h
xen/include/asm-x86/vmx_vlapic.h

index 63bdc25d3abb0d20456419376c9b984460da7717..540543a991f988b5ec85f01c5a2f769028f12027 100644 (file)
@@ -26,6 +26,9 @@ name = "ExampleVMXDomain"
 # Which CPU to start domain on? 
 #cpu = -1   # leave to Xen to pick
 
+# Disable vif for now
+nics=0
+
 # Optionally define mac and/or bridge for the network interfaces.
 # Random MACs are assigned if not given.
 #vif = [ 'mac=aa:00:00:00:00:11, bridge=xen-br0' ]
index c0d637ff850a9678092a617c79310e60fef511b7..07ea6be0f80450b78445adfe1982e15472399c39 100644 (file)
@@ -236,6 +236,7 @@ u64_t _InterlockedCompareExchange64_acq(volatile uint64_t *dest, uint64_t xchg,
 #define __ia64_fc(addr)        asm volatile ("fc %0" :: "r"(addr) : "memory")
 #define ia64_sync_i()  asm volatile (";; sync.i" ::: "memory")
 
+register unsigned long ia64_r13 asm ("r13") __attribute_used__;
 #define __ia64_getreg(regnum)                                                  \
 ({                                                                             \
        uint64_t ia64_intri_res;                                                        \
index c05013f75cab1c45a94be693e48268801c53baa2..ba4926bfa7b77b77fdc7b8333d1d3f9a2adbb305 100644 (file)
@@ -188,7 +188,7 @@ endif
 #########################################################
 
 DEFINES+=-D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE
-LIBS+=-lm -L../../libxc -lxenctrl
+LIBS+=-lm -L../../libxc -lxenctrl -lxenguest
 ifndef CONFIG_USER_ONLY
 LIBS+=-lz
 endif
index 3ea7828412be1183f57b8ab921dcb0e28251d954..294e3bcdc71b91bc0f51d7a20bd6d423c1c60150 100644 (file)
@@ -523,8 +523,8 @@ int64_t cpu_get_real_ticks(void)
 
 #elif defined(__ia64__)
 #include "ia64_intrinsic.h"
-#define cpu_get_reak_ticks()   \
-    ia64_getreg(_IA64_REG_AR_ITC)
+#define cpu_get_real_ticks()   \
+       __ia64_getreg(_IA64_REG_AR_ITC)
 
 #else
 #error unsupported CPU
index b21959b8d26972da340bd1282b55c309dc1910e0..c246cbbdc61a6be405186ed9db1b5545226f7cba 100644 (file)
@@ -603,6 +603,7 @@ int xc_vmx_build(int xc_handle,
                  int memsize,
                  const char *image_name,
                  unsigned int control_evtchn,
+                unsigned int lapic,
                  unsigned int vcpus,
                  unsigned int store_evtchn,
                  unsigned long *store_mfn)
index de4a64f11a284a0c92fce8523da8690025f6f106..49ed75e52d40dfe6bd3ceb31295fba5fa2f121f6 100644 (file)
@@ -783,7 +783,7 @@ int xc_linux_build(int xc_handle,
     /* currently done by hypervisor, should move here */
     /* ctxt->regs.r28 = dom_fw_setup(); */
     ctxt->vcpu.privregs = 0;
-    ctxt->sys_pgnr = nr_pages - 3;
+    ctxt->sys_pgnr = 3;
     i = 0; /* silence unused variable warning */
 #else /* x86 */
     /*
index 3eabd0b7ed7aa4192baafcb716f754fc1990ced9..08bc8aafe1621e372737207388efb37c835318eb 100644 (file)
@@ -15,7 +15,7 @@ OBJS = xensetup.o setup.o time.o irq.o ia64_ksyms.o process.o smp.o \
 OBJS += vmx_init.o vmx_virt.o vmx_vcpu.o vmx_process.o vmx_vsa.o vmx_ivt.o\
        vmx_phy_mode.o vmx_utility.o vmx_interrupt.o vmx_entry.o vmmu.o \
        vtlb.o mmio.o vlsapic.o vmx_hypercall.o mm.o vmx_support.o \
-       pal_emul.o vmx_irq_ia64.o
+       pal_emul.o vmx_irq_ia64.o vmx_vioapic.o
 
 # lib files from xen/arch/ia64/linux/ (linux/arch/ia64/lib)
 OBJS +=        bitop.o clear_page.o flush.o copy_page_mck.o                    \
@@ -68,6 +68,11 @@ $(BASEDIR)/include/asm-ia64/.offsets.h.stamp:
         || ln -s $(BASEDIR)/include/xen $(BASEDIR)/include/linux
        [ -e $(BASEDIR)/include/asm-ia64/xen ] \
         || ln -s $(BASEDIR)/include/asm-ia64/linux $(BASEDIR)/include/asm-ia64/xen
+# Link to DM file in Xen for ia64/vti
+       [ -e $(BASEDIR)/include/asm-ia64/vmx_vioapic.h ] \
+        || ln -s ../../include/asm-x86/vmx_vioapic.h $(BASEDIR)/include/asm-ia64/vmx_vioapic.h
+       [ -e $(BASEDIR)/arch/ia64/vmx/vmx_vioapic.c ] \
+        || ln -s ../../../arch/x86/dm/vmx_vioapic.c $(BASEDIR)/arch/ia64/vmx/vmx_vioapic.c
 # Solve circular reference on asm-offsets.h
        [ -f $(BASEDIR)/include/asm-ia64/asm-offsets.h ] \
         || echo "#define IA64_TASK_SIZE 0" > $(BASEDIR)/include/asm-ia64/asm-offsets.h
index 8eb31cc674be949d378be8fea4d5dd4616ac126a..279761d893a2715ff7b205e10ae3e6aa29fe7451 100644 (file)
@@ -24,7 +24,7 @@ CFLAGS  += -I$(BASEDIR)/include/asm-ia64 -I$(BASEDIR)/include/asm-ia64/linux \
           -I$(BASEDIR)/include/asm-ia64/linux-null                     \
            -I$(BASEDIR)/arch/ia64/linux -I$(BASEDIR)/arch/ia64/linux-xen
 CFLAGS  += -Wno-pointer-arith -Wredundant-decls
-CFLAGS  += -DIA64 -DXEN -DLINUX_2_6
+CFLAGS  += -DIA64 -DXEN -DLINUX_2_6 -DV_IOSAPIC_READY
 CFLAGS += -ffixed-r13 -mfixed-range=f12-f15,f32-f127
 CFLAGS += -w -g
 ifeq ($(VALIDATE_VT),y)
index f603fb7351cdd68bc576b1a4abd650ce2fa73ad6..a64c16829c1b08fdfe734b85094d11775677c74c 100644 (file)
@@ -202,11 +202,13 @@ static void legacy_io_access(VCPU *vcpu, u64 pa, u64 *val, size_t s, int dir)
     return;
 }
 
+extern struct vmx_mmio_handler vioapic_mmio_handler;
 static void mmio_access(VCPU *vcpu, u64 src_pa, u64 *dest, size_t s, int ma, int dir)
 {
     struct virutal_platform_def *v_plat;
     //mmio_type_t iot;
     unsigned long iot;
+    struct vmx_mmio_handler *vioapic_handler = &vioapic_mmio_handler;
     iot=__gpfn_is_io(vcpu->domain, src_pa>>PAGE_SHIFT);
     v_plat = vmx_vcpu_get_plat(vcpu);
 
@@ -220,6 +222,11 @@ static void mmio_access(VCPU *vcpu, u64 src_pa, u64 *dest, size_t s, int ma, int
     case GPFN_GFW:
         break;
     case GPFN_IOSAPIC:
+       if (!dir)
+           vioapic_handler->write_handler(vcpu, src_pa, s, *dest);
+       else
+           *dest = vioapic_handler->read_handler(vcpu, src_pa, s);
+       break;
     case GPFN_FRAME_BUFFER:
     case GPFN_LOW_MMIO:
         low_mmio_access(vcpu, src_pa, dest, s, dir);
index 4034fbe4571f943412071bfc7cc93615b6ad7070..340bdd40c410361b22a452bcf239892bae49e528 100644 (file)
 #include <asm/hw_irq.h>
 #include <asm/vmx_pal_vsa.h>
 #include <asm/kregs.h>
+#include <asm/vmx_platform.h>
+#include <asm/vmx_vioapic.h>
 
-#define  SHARED_VLAPIC_INF
-#ifdef V_IOSAPIC_READY
-static inline vl_apic_info* get_psapic(VCPU *vcpu)
-{
-    shared_iopage_t  *sp = get_sp(vcpu->domain);
-    return &(sp->vcpu_iodata[vcpu->vcpu_id].apic_intr);
-}
-#endif
 //u64  fire_itc;
 //u64  fire_itc2;
 //u64  fire_itm;
@@ -273,48 +267,71 @@ static void update_vhpi(VCPU *vcpu, int vec)
 }
 
 #ifdef V_IOSAPIC_READY
-void vlapic_update_shared_info(VCPU *vcpu)
-{
-    //int      i;
-    
-    vl_apic_info *ps;
-
-    if (vcpu->domain == dom0)
-       return;
-
-    ps = get_psapic(vcpu);
-    ps->vl_lapic_id = ((VCPU(vcpu, lid) >> 16) & 0xffff) << 16; 
-    printf("vl_lapic_id = %x\n", ps->vl_lapic_id);
-    ps->vl_apr = 0;
-    // skip ps->vl_logical_dest && ps->vl_dest_format
-    // IPF support physical destination mode only
-    ps->vl_arb_id = 0;
-    /*
-    for ( i=0; i<4; i++ ) {
-       ps->tmr[i] = 0;         // edge trigger 
+/* Assist to check virtual interrupt lines */
+void vmx_virq_line_assist(struct vcpu *v)
+{
+    global_iodata_t *spg = &get_sp(v->domain)->sp_global;
+    uint16_t *virq_line, irqs;
+
+    virq_line = &spg->pic_irr;
+    if (*virq_line) {
+       do {
+           irqs = *(volatile uint16_t*)virq_line;
+       } while ((uint16_t)cmpxchg(virq_line, irqs, 0) != irqs);
+       vmx_vioapic_do_irqs(v->domain, irqs);
     }
-    */
+
+    virq_line = &spg->pic_clear_irr;
+    if (*virq_line) {
+       do {
+           irqs = *(volatile uint16_t*)virq_line;
+       } while ((uint16_t)cmpxchg(virq_line, irqs, 0) != irqs);
+       vmx_vioapic_do_irqs_clear(v->domain, irqs);
+    }
+}
+
+void vmx_virq_line_init(struct domain *d)
+{
+    global_iodata_t *spg = &get_sp(d)->sp_global;
+
+    spg->pic_elcr = 0xdef8; /* Level/Edge trigger mode */
+    spg->pic_irr = 0;
+    spg->pic_last_irr = 0;
+    spg->pic_clear_irr = 0;
 }
 
-void vlapic_update_ext_irq(VCPU *vcpu)
+int ioapic_match_logical_addr(vmx_vioapic_t *s, int number, uint16_t dest)
 {
-    int  vec;
+    return (VLAPIC_ID(s->lapic_info[number]) == dest);
+}
+
+struct vlapic* apic_round_robin(struct domain *d,
+                               uint8_t dest_mode,
+                               uint8_t vector,
+                               uint32_t bitmap)
+{
+    uint8_t bit;
+    vmx_vioapic_t *s;
     
-    vl_apic_info *ps = get_psapic(vcpu);
-    while ( (vec = highest_bits(ps->irr)) != NULL_VECTOR ) {
-       clear_bit (vec, ps->irr);
-        vmx_vcpu_pend_interrupt(vcpu, vec);
+    if (!bitmap) {
+       printk("<apic_round_robin> no bit on bitmap\n");
+       return NULL;
     }
+
+    s = &d->arch.vmx_platform.vmx_vioapic;
+    for (bit = 0; bit < s->lapic_count; bit++) {
+       if (bitmap & (1 << bit))
+           return s->lapic_info[bit];
+    }
+
+    return NULL;
 }
 #endif
 
 void vlsapic_reset(VCPU *vcpu)
 {
     int     i;
-#ifdef V_IOSAPIC_READY
-    vl_apic_info  *psapic;     // shared lapic inf.
-#endif
-    
+
     VCPU(vcpu, lid) = ia64_getreg(_IA64_REG_CR_LID);
     VCPU(vcpu, ivr) = 0;
     VCPU(vcpu,tpr) = 0x10000;
@@ -331,9 +348,10 @@ void vlsapic_reset(VCPU *vcpu)
     for ( i=0; i<4; i++) {
         VLSAPIC_INSVC(vcpu,i) = 0;
     }
+
 #ifdef V_IOSAPIC_READY
-    vlapic_update_shared_info(vcpu);
-    //vlapic_update_shared_irr(vcpu);
+    vcpu->arch.arch_vmx.vlapic.vcpu = vcpu;
+    vmx_vioapic_add_lapic(&vcpu->arch.arch_vmx.vlapic, vcpu);
 #endif
     DPRINTK("VLSAPIC inservice base=%lp\n", &VLSAPIC_INSVC(vcpu,0) );
 }
index 452a96e0932b0396bc3f530cb7ff527ce7b316d1..3334b0c77d90dba6a63d5570f0b4a7fccffd3a5b 100644 (file)
 #include <asm/vmx.h>
 #include <xen/mm.h>
 #include <public/arch-ia64.h>
+#include <asm/vmx_vioapic.h>
 
 /* Global flag to identify whether Intel vmx feature is on */
 u32 vmx_enabled = 0;
+unsigned int opt_vmx_debug_level = 0;
 static u32 vm_order;
 static u64 buffer_size;
 static u64 vp_env_info;
@@ -307,9 +309,8 @@ vmx_change_double_mapping(struct vcpu *v, u64 oldrr7, u64 newrr7)
  * is registered here.
  */
 void
-vmx_final_setup_domain(struct domain *d)
+vmx_final_setup_guest(struct vcpu *v)
 {
-       struct vcpu *v = d->vcpu[0];
        vpd_t *vpd;
 
        /* Allocate resources for vcpu 0 */
@@ -318,8 +319,7 @@ vmx_final_setup_domain(struct domain *d)
        vpd = alloc_vpd();
        ASSERT(vpd);
 
-//     v->arch.arch_vmx.vpd = vpd;
-    v->arch.privregs = vpd;
+       v->arch.privregs = vpd;
        vpd->virt_env_vaddr = vm_buffer;
 
        /* Per-domain vTLB and vhpt implementation. Now vmx domain will stick
@@ -341,7 +341,8 @@ vmx_final_setup_domain(struct domain *d)
        vlsapic_reset(v);
        vtm_init(v);
 
-       /* Other vmx specific initialization work */
+       /* One more step to enable interrupt assist */
+       set_bit(ARCH_VMX_INTR_ASSIST, &v->arch.arch_vmx.flags);
 }
 
 typedef struct io_range {
@@ -431,9 +432,8 @@ int vmx_alloc_contig_pages(struct domain *d)
        return 0;
 }
 
-void vmx_setup_platform(struct vcpu *v, struct vcpu_guest_context *c)
+void vmx_setup_platform(struct domain *d, struct vcpu_guest_context *c)
 {
-       struct domain *d = v->domain;
        shared_iopage_t *sp;
 
        ASSERT(d != dom0); /* only for non-privileged vti domain */
@@ -441,27 +441,19 @@ void vmx_setup_platform(struct vcpu *v, struct vcpu_guest_context *c)
                __va(__gpa_to_mpa(d, IO_PAGE_START));
        sp = get_sp(d);
        //memset((char *)sp,0,PAGE_SIZE);
-       //sp->sp_global.eport = 2;
-#ifdef V_IOSAPIC_READY
-       sp->vcpu_number = 1;
-#endif
        /* TEMP */
        d->arch.vmx_platform.pib_base = 0xfee00000UL;
 
-       /* One more step to enable interrupt assist */
-       set_bit(ARCH_VMX_INTR_ASSIST, &v->arch.arch_vmx.flags);
        /* Only open one port for I/O and interrupt emulation */
-       if (v == d->vcpu[0]) {
-           memset(&d->shared_info->evtchn_mask[0], 0xff,
-               sizeof(d->shared_info->evtchn_mask));
-           clear_bit(iopacket_port(d), &d->shared_info->evtchn_mask[0]);
-       }
-
-       /* FIXME: only support PMT table continuously by far */
-//     d->arch.pmt = __va(c->pt_base);
+       memset(&d->shared_info->evtchn_mask[0], 0xff,
+           sizeof(d->shared_info->evtchn_mask));
+       clear_bit(iopacket_port(d), &d->shared_info->evtchn_mask[0]);
 
+       /* Initialize the virtual interrupt lines */
+       vmx_virq_line_init(d);
 
-       vmx_final_setup_domain(d);
+       /* Initialize iosapic model within hypervisor */
+       vmx_vioapic_init(d);
 }
 
 
index 25f3db74ecf3f0df8b166a5ea6220e542f918f43..19ea7be6de97889c5b3ffb101ccb4c410dd97a46 100644 (file)
@@ -156,9 +156,8 @@ void vmx_intr_assist(struct vcpu *v)
        panic("Corruption: bad shared page: %lx\n", (unsigned long)vio);
 
 #ifdef V_IOSAPIC_READY
-    vlapic_update_ext_irq(v);
-#else
-    //panic("IOSAPIC model is missed in qemu\n");
+    /* Confirm virtual interrupt line signals, and set pending bits in vpd */
+    vmx_virq_line_assist(v);
 #endif
     return;
 }
index 8cf6c86cde2772a9a7d03d86bc25187975d7e4cf..15920ca8a02768e8d3f9793e8b6d8b431442bd9f 100644 (file)
@@ -293,10 +293,14 @@ int arch_set_info_guest(struct vcpu *v, struct vcpu_guest_context *c)
                return -EINVAL;
            }
 
-           vmx_setup_platform(v, c);
+           if (v == d->vcpu[0])
+               vmx_setup_platform(d, c);
+
+           vmx_final_setup_guest(v);
        }
 
        *regs = c->regs;
+       d->arch.sys_pgnr = c->sys_pgnr;
        new_thread(v, regs->cr_iip, 0, 0);
 
        v->vcpu_info->arch.evtchn_vector = c->vcpu.evtchn_vector;
@@ -307,7 +311,6 @@ int arch_set_info_guest(struct vcpu *v, struct vcpu_guest_context *c)
        }
 
        v->arch.domain_itm_last = -1L;
-       d->arch.sys_pgnr = c->sys_pgnr;
        d->shared_info->arch = c->shared;
 
        /* Don't redo final setup */
@@ -991,7 +994,7 @@ int construct_dom0(struct domain *d,
         */
        printk("Dom0: 0x%lx, domain: 0x%lx\n", (u64)dom0, (u64)d);
        if (vmx_dom0)
-           vmx_final_setup_domain(dom0);
+           vmx_final_setup_guest(v);
 
        set_bit(_VCPUF_initialised, &v->vcpu_flags);
 
index b36a1b7bc80627d501dcbd357f9bbe66214ecfa7..8f74f74eb4265566387dd0251a4641dcbba171fb 100644 (file)
@@ -297,12 +297,14 @@ static int ioapic_inj_irq(vmx_vioapic_t *s,
     switch (delivery_mode) {
     case VLAPIC_DELIV_MODE_FIXED:
     case VLAPIC_DELIV_MODE_LPRI:
-        if (test_and_set_bit(vector, &target->irr[0]) && trig_mode == 1) {
+        if (test_and_set_bit(vector, &VLAPIC_IRR(target)) && trig_mode == 1) {
             /* the level interrupt should not happen before it is cleard */
             printk("<ioapic_inj_irq> level interrupt happen before cleard\n");
         }
+#ifndef __ia64__
         if (trig_mode)
             test_and_set_bit(vector, &target->tmr[0]);
+#endif
         result = 1;
         break;
     default:
@@ -367,7 +369,7 @@ static uint32_t ioapic_get_delivery_bitmask(vmx_vioapic_t *s,
 
     if (dest_mode == 0) { /* Physical mode */
         for (i = 0; i < s->lapic_count; i++) {
-            if (s->lapic_info[i]->id == dest) {
+            if (VLAPIC_ID(s->lapic_info[i]) == dest) {
                 mask = 1 << i;
                 break;
             }
index cdded3dfd2a17929892d9f3c0d300e1b28a3b881..8e21eec0d9dba3cb5422fb71420693c17f9ff651 100644 (file)
 #define RR7_SWITCH_SHIFT       12      /* 4k enough */
 #include <public/io/ioreq.h>
 
-
 extern void identify_vmx_feature(void);
 extern unsigned int vmx_enabled;
 extern void vmx_init_env(void);
-extern void vmx_final_setup_domain(struct domain *d);
+extern void vmx_final_setup_guest(struct vcpu *v);
 extern void vmx_save_state(struct vcpu *v);
 extern void vmx_load_state(struct vcpu *v);
-extern void vmx_setup_platform(struct vcpu *v, struct vcpu_guest_context *c);
+extern void vmx_setup_platform(struct domain *d, struct vcpu_guest_context *c);
 #ifdef XEN_DBL_MAPPING
 extern vmx_insert_double_mapping(u64,u64,u64,u64,u64);
 extern void vmx_purge_double_mapping(u64, u64, u64);
@@ -57,4 +56,22 @@ static inline shared_iopage_t *get_sp(struct domain *d)
 {
     return (shared_iopage_t *)d->arch.vmx_platform.shared_page_va;
 }
+
+typedef unsigned long (*vmx_mmio_read_t)(struct vcpu *v,
+                                         unsigned long addr,
+                                         unsigned long length);
+
+typedef void (*vmx_mmio_write_t)(struct vcpu *v,
+                                 unsigned long addr,
+                                 unsigned long length,
+                                 unsigned long val);
+
+typedef int (*vmx_mmio_check_t)(struct vcpu *v, unsigned long addr);
+
+struct vmx_mmio_handler {
+    vmx_mmio_check_t check_handler;
+    vmx_mmio_read_t read_handler;
+    vmx_mmio_write_t write_handler;
+};
+
 #endif /* _ASM_IA64_VT_H */
index 37560863fa66359232fb5b94895b1dc2ecfbed76..e36188898adb5d0c33e68ea115fb8f29432f455b 100644 (file)
 #define __ASM_IA64_VMX_PLATFORM_H__
 
 #include <public/xen.h>
-
+#include <public/arch-ia64.h>
+#include <asm/vmx_vioapic.h>
 
 struct mmio_list;
 typedef struct virutal_platform_def {
-    //unsigned long          *real_mode_data; /* E820, etc. */
-    unsigned long          shared_page_va;
-    //struct vmx_virpit_t    vmx_pit;
-    //struct vmx_handler_t   vmx_handler;
-    //struct mi_per_cpu_info mpci;            /* MMIO */
+    unsigned long       shared_page_va;
     unsigned long       pib_base;
     unsigned char       xtp;
     struct mmio_list    *mmio;
+    /* One IOSAPIC now... */
+    struct vmx_vioapic   vmx_vioapic;
 } vir_plat_t;
 
+static inline int __fls(uint32_t word)
+{
+    long double d = word;
+    long exp;
+
+    __asm__ __volatile__ ("getf.exp %0=%1" : "=r"(exp) : "f"(d));
+    return word ? (exp - 0xffff) : -1;
+}
+
+/* This is a connect structure between vIOSAPIC model and vLSAPIC model.
+ * vlapic is required by vIOSAPIC model to manipulate pending bits, and
+ * we just map them into vpd here
+ */
+typedef struct vlapic {
+    struct vcpu        *vcpu;  /* Link to current vcpu */
+} vlapic_t;
+
+extern uint64_t dummy_tmr[];
+#define VCPU(_v,_x)    _v->arch.privregs->_x
+#define VLAPIC_ID(l) (uint16_t)(VCPU((l)->vcpu, lid) >> 16)
+#define VLAPIC_IRR(l) VCPU((l)->vcpu, irr[0])
+
+/* As long as we register vlsapic to ioapic controller, it's said enabled */
+#define vlapic_enabled(l) 1
+#define vmx_apic_support(d) 1
+
+#define VLAPIC_DELIV_MODE_FIXED                0x0
+#define VLAPIC_DELIV_MODE_REDIR                0x1
+#define VLAPIC_DELIV_MODE_LPRI         VLAPIC_DELIV_MODE_REDIR
+#define VLAPIC_DELIV_MODE_PMI          0x2
+#define VLAPIC_DELIV_MODE_SMI          0x2 /* For IA32 */
+#define VLAPIC_DELIV_MODE_RESERVED     0x3
+#define VLAPIC_DELIV_MODE_NMI          0x4
+#define VLAPIC_DELIV_MODE_INIT         0x5
+#define VLAPIC_DELIV_MODE_STARTUP      0x6 /* For IA32 */
+#define VLAPIC_DELIV_MODE_EXT          0x7
+
 #endif
index f0729b3e0aa7b0c09eb9d60969318d68508cdeab..509e3732a6359cf7d590527f794f7b929c4d35da 100644 (file)
@@ -107,10 +107,6 @@ extern void vtm_set_itv(VCPU *vcpu);
 extern void vtm_interruption_update(VCPU *vcpu, vtime_t* vtm);
 extern void vtm_domain_out(VCPU *vcpu);
 extern void vtm_domain_in(VCPU *vcpu);
-#ifdef V_IOSAPIC_READY
-extern void vlapic_update_ext_irq(VCPU *vcpu);
-extern void vlapic_update_shared_info(VCPU *vcpu);
-#endif
 extern void vlsapic_reset(VCPU *vcpu);
 extern int vmx_check_pending_irq(VCPU *vcpu);
 extern void guest_write_eoi(VCPU *vcpu);
@@ -278,9 +274,6 @@ IA64FAULT
 vmx_vcpu_set_lid(VCPU *vcpu, u64 val)
 {
     VCPU(vcpu,lid)=val;
-#ifdef V_IOSAPIC_READY
-    vlapic_update_shared_info(vcpu);
-#endif
     return IA64_NO_FAULT;
 }
 extern IA64FAULT vmx_vcpu_set_tpr(VCPU *vcpu, u64 val);
index 04fd57c15166dd2c03d844661a8014c4d3915737..4f0e74aaae857558fe814edc5631cfe5ca49f89b 100644 (file)
@@ -25,6 +25,7 @@
 #ifndef __ASSEMBLY__
 
 #include <asm/vtm.h>
+#include <asm/vmx_platform.h>
 #include <public/arch-ia64.h>
 
 #define VPD_SHIFT      17      /* 128K requirement */
@@ -65,7 +66,8 @@ typedef struct {
 struct arch_vmx_struct {
 //    struct virutal_platform_def     vmx_platform;
 //     vpd_t       *vpd;
-       vtime_t     vtm;
+    vtime_t        vtm;
+    struct vlapic   vlapic;
     unsigned long   vrr[8];
     unsigned long   vkr[8];
     unsigned long   cr_iipa;   /* for emulation */
@@ -106,6 +108,7 @@ struct arch_vmx_struct {
 #define DBG_LEVEL_3     (1 << 3)
 #define DBG_LEVEL_IO    (1 << 4)
 #define DBG_LEVEL_VMMU  (1 << 5)
+#define DBG_LEVEL_IOAPIC       (1 << 6)
 
 extern unsigned int opt_vmx_debug_level;
 #define VMX_DBG_LOG(level, _f, _a...)           \
index 9f0f5bd89749c32f1a3f9fa0ad5d433750b2ed66..98fc0bf30a1e0939dfe8394a8b51fc014ccb5f75 100644 (file)
 
 #define IOAPIC_REG_VERSION 0x1
 
-#ifdef __ia64__
-typedef union RedirStatus
-{
-    uint64_t value;
-    struct {
-        uint16_t dest_id;
-        uint8_t reserved[3];
-        uint8_t reserve:7;
-        uint8_t mask:1;         /* interrupt mask*/
-        uint8_t trigmod:1;
-        uint8_t remoteirr:1;
-        uint8_t polarity:1;
-        uint8_t delivestatus:1;
-        uint8_t destmode:1;
-        uint8_t deliver_mode:3;
-        uint8_t vector;
-    } RedirForm;
-} RedirStatus;
-#else
 typedef union RedirStatus
 {
     uint64_t value;
@@ -95,11 +76,15 @@ typedef union RedirStatus
         uint8_t trigmod:1;
         uint8_t mask:1;         /* interrupt mask*/
         uint8_t reserve:7;
+#ifndef __ia64__
         uint8_t reserved[4];
         uint8_t dest_id;
+#else
+        uint8_t reserved[3];
+        uint16_t dest_id;
+#endif
     } RedirForm;
 } RedirStatus;
-#endif
 
 #define IOAPIC_MEM_LENGTH    0x100
 #define IOAPIC_ENABLE_MASK   0x0
index 24a09e0096a149b488eaf563968910b4965139d5..991a6f36c168ec2a82d0f28d36ec8fd02a38400e 100644 (file)
@@ -151,6 +151,9 @@ static __inline__ int find_highest_bit(uint32_t *data, int length)
 #define vlapic_global_enabled(vlapic)               \
   !(test_bit(_VLAPIC_GLOB_DISABLE, &(vlapic)->status))
 
+#define VLAPIC_IRR(t) ((t)->irr[0])
+#define VLAPIC_ID(t)  ((t)->id)
+
 typedef struct direct_intr_info {
     int deliver_mode;
     int source[6];